home *** CD-ROM | disk | FTP | other *** search
/ Developer CD Series 1995…tember: Reference Library / Dev.CD Sep 95 RL / Dev.CD Sep 95 RL.toast / mac / Technical Documentation / develop / develop Issue 12 code / Components / Sources / NuMathComponent.c < prev    next >
Encoding:
Text File  |  1994-12-02  |  12.3 KB  |  442 lines  |  [TEXT/MMCC]

  1. /************************************************************************************
  2.  
  3.     File:        NuMathComponent.c
  4.  
  5.     Contains:    NuMath component routines.
  6.  
  7.     Written by:    Gary Woodcock
  8.  
  9.     Copyright:    © 1992 by Apple Computer, Inc.
  10.  
  11.     Change History (most recent first):
  12.             
  13.     Project settings for 68K
  14.         Code model:                 Small, Smart or Large
  15.         Link Single Segment:        on (VERY important)
  16.         Project type:                Code Resource
  17.         File name:                    NuMath_Component
  18.         Sym name:                    NuMath_Component.SYM (not generated)
  19.         Resource name:                Extended Math Component
  20.         Header type:                Standard
  21.         Multi Segment:                 on or off
  22.         ResType:                    _68K
  23.         ID:                            132 
  24.         SegType                        blank (unused since we are linking single segment)
  25.         Creator:                    gwck
  26.         File type:                    thng
  27.         Resource flags:                SysHeap
  28.         Project setup:
  29.             Segment 1 (Main Segment): NuMathComponent.c
  30.             Segment 2 (Group2): MacOS.lib, FatNuMathComponent.rsrc (See warning below)
  31.             Segment 3 (Group3): and MathComponentCommon.c
  32.                         
  33.     Project settings for PPC 
  34.         Project type:                Code Resource
  35.         File name:                    NuMath_Component
  36.         Sym name:                    NuMath_Component.SYM (not generated)
  37.         Resource name:                Extended Math Component
  38.         Header type:                None (VERY important)
  39.         ResType:                    _PPc
  40.         ID:                            130 
  41.         Creator:                    gwck
  42.         File type:                    thng
  43.         Resource flags:                SysHeap
  44.         Merge To File                on
  45.         Expand Uninitialized Data:     on
  46.         Main Entry Point            MainRD (VERY important)
  47.         Project setup:
  48.             Group 1 (Main Group): NuMathComponent.c, PPCGlue.c
  49.             Group 2 (Group2): InterfaceLib, MathLib, ToolsLib.o
  50.             Group 3 (Group3): MathComponentCommon.c
  51.                         
  52.     ***Warning*** FatNuMathComponent.rsrc has an extended thng resource which 
  53.     is set to require both PPC and 68K code.  If you want to test the 68K 
  54.     component by itself, use NuMathComponent.rsrc, instead.
  55.  
  56.     CW components need to have the Link Single Segment switch checked.  The Multi-
  57.     segment switch can be checked or unchecked as fits your needs.  (Please 
  58.     see the User Guide for which situations require the Multi-segment switch.)
  59.     Putting everything into one segment eliminates segment loader errors that 
  60.     would occur if the startup code tried to call GetResource before 
  61.     OpenComponentResFile is called.  Components written in C are moveable, components 
  62.     written in C++ with virtual functions probably aren't.  Please see the 
  63.     C++ XCMD example on the CD for an example of how to deal C++ code resources.
  64.  
  65.     Project settings, port to PPC and comments by
  66.     Mark Anderson
  67.     metrowerks
  68.     12/1/94
  69.     
  70. ************************************************************************************/
  71.  
  72. //-----------------------------------------------------------------------
  73. // Includes
  74.  
  75. #include "MathComponent.h"
  76. #include "MathComponentPrivate.h"
  77. #include "NuMathComponentPrivate.h"
  78. #include <FixMath.h>
  79. #ifndef powerc
  80.     #include <A4Stuff.h>
  81. #endif
  82.  
  83. //-----------------------------------------------------------------------
  84. // Prototype (can't be in header or there is a conflict with Component Tester)
  85. #ifndef DEBUG_IT
  86.     pascal    ComponentResult    main    (ComponentParameters    *params,
  87.                                  Handle                    storage);
  88. #endif
  89.  
  90. //-----------------------------------------------------------------------
  91. //PPC Globals
  92. #ifdef powerc
  93. INSTANTIATE_ROUTINE_DESCRIPTOR(NuMathOpen);
  94. INSTANTIATE_ROUTINE_DESCRIPTOR(NuMathClose);
  95. INSTANTIATE_ROUTINE_DESCRIPTOR(NuMathCanDo);
  96. INSTANTIATE_ROUTINE_DESCRIPTOR(NuMathVersion);
  97. INSTANTIATE_ROUTINE_DESCRIPTOR(NuMathRegister);
  98. INSTANTIATE_ROUTINE_DESCRIPTOR(NuMathDoDivide);
  99. INSTANTIATE_ROUTINE_DESCRIPTOR(NuMathDoMultiply);
  100.  
  101. #ifndef DEBUG_IT
  102.     RoutineDescriptor MainRD = BUILD_ROUTINE_DESCRIPTOR(uppComponentRoutineProcInfo, main);
  103.     ProcInfoType __procinfo = uppComponentRoutineProcInfo;
  104. #endif
  105. #endif
  106.  
  107. //-----------------------------------------------------------------------
  108. #ifdef DEBUG_IT
  109.  
  110. // Use this declaration when we're running linked (for debugging)
  111. pascal    ComponentResult    NuMathDispatcher    (ComponentParameters    *params,
  112.                                              Handle                    storage)
  113.                                              
  114. #else
  115.  
  116. // Use this declaration when we're a standalone component
  117. pascal    ComponentResult    main    (ComponentParameters    *params,
  118.                                  Handle                    storage)
  119.  
  120. #endif DEBUG_IT
  121.  
  122. {
  123.     // This routine is the main dispatcher for the NuMath component
  124.     
  125.  
  126.     ComponentResult    result = noErr;
  127.  
  128. #if !defined(powerc) && !defined(DEBUG_IT)
  129.     long             oldA4;
  130.     
  131.     oldA4 = SetCurrentA4();
  132. #endif
  133.  
  134.     // Did we get a Component Manager request code (< 0)?
  135.     if (params->what < 0)
  136.     {
  137.         switch (params->what)
  138.         {
  139.             case kComponentOpenSelect:        // Open request
  140.             {
  141.                 result = CallComponentFunctionUniv(params, NuMathOpen);
  142.                 break;
  143.             }
  144.             case kComponentCloseSelect:        // Close request
  145.             {
  146.                 //if open fails, close gets called (why I don't know) so 
  147.                 //globals aren't allocated
  148.                 if (!storage)
  149.                     return result;
  150.                 result = CallComponentFunctionWithStorageUniv(storage, params, NuMathClose);
  151.                 break;    
  152.             }
  153.             case kComponentCanDoSelect:        // Can Do request
  154.             {
  155.                 result = CallComponentFunctionUniv(params, NuMathCanDo);
  156.                 break;    
  157.             }
  158.             case kComponentVersionSelect:    // Version request
  159.             {
  160.                 result = CallComponentFunctionUniv(params, NuMathVersion);
  161.                 break;    
  162.             }
  163.             case kComponentRegisterSelect:    // Register request
  164.             {
  165.                 result = CallComponentFunctionUniv(params, NuMathRegister);
  166.                 break;    
  167.             }
  168.             case kComponentTargetSelect:    // Target request not supported
  169.             default:                        // Unknown request
  170.             {
  171.                 result = paramErr;
  172.                 break;
  173.             }
  174.         }
  175.     }
  176.     else    // Was it one of our request codes?
  177.     {
  178.         switch (params->what)
  179.         {
  180.             case kDoDivideSelect:            // Divide request
  181.             {
  182.                 result = CallComponentFunctionUniv(params, NuMathDoDivide);
  183.                 break;    
  184.             }
  185.             
  186.             case kDoMultiplySelect:            // Multiply request
  187.             {    
  188.                 result = CallComponentFunctionWithStorageUniv(storage, params, NuMathDoMultiply);
  189.                 break;    
  190.             }
  191.  
  192.             default:                        // Unknown request
  193.             {
  194.                 result = paramErr;
  195.                 break;
  196.             }
  197.         }
  198.     }
  199.  
  200. #if !defined(powerc) && !defined(DEBUG_IT)
  201.     SetA4(oldA4);
  202. #endif
  203.  
  204.     return (result);
  205. }
  206.                                              
  207. //-----------------------------------------------------------------------
  208.  
  209. pascal    ComponentResult    NuMathOpen    (ComponentInstance    self)
  210. {
  211.     ComponentResult        result = noErr;
  212.     PrivateGlobals**    globals; 
  213.  
  214.     // Can we open another instance?
  215.  
  216.     if (CountComponentInstances ((Component) self) <= kMaxNuMathInstances)
  217.     {
  218.         // Did we get our storage?
  219.         globals = (PrivateGlobals**) NewHandleClear (sizeof (PrivateGlobals));
  220.         if (globals != nil)
  221.         {
  222.             ComponentDescription    delegateDesc;
  223.             Component                delegateComponent = nil;
  224.             ComponentInstance        delegateComponentInstance;
  225.             Component                selfComponent;
  226.             ComponentDescription    tempDesc;
  227.             
  228.             // Keep a reference to self
  229.             (*globals)->self = (Component) self;
  230.  
  231.             // Describe the component we want to capture
  232.             delegateDesc.componentType = mathComponentType;
  233.             delegateDesc.componentSubType = 0L;
  234.             delegateDesc.componentManufacturer = 'appl';
  235.             delegateDesc.componentFlags = 0L;
  236.             delegateDesc.componentFlagsMask = 0L;
  237.             
  238.             // Keep track of which component we are by querying
  239.             // the component info; the componentFlagsMask will
  240.             // contain the component ID for the component we
  241.             // are requesting info for
  242.             result = GetComponentInfo ((Component) self, &tempDesc, nil, nil, nil);
  243.             selfComponent = (Component)(tempDesc.componentFlagsMask);
  244.             
  245.             // Find the component we want to capture
  246.             do
  247.             {
  248.                 delegateComponent = FindNextComponent (delegateComponent, &delegateDesc);
  249.             }
  250.             while (delegateComponent == selfComponent);
  251.             
  252.             // Did we find one?
  253.             if (delegateComponent != 0L)
  254.             {
  255.                 // Can this component be captured (does it support the
  256.                 // target request code)?
  257.                 if (ComponentFunctionImplemented ((ComponentInstance) delegateComponent,
  258.                     kComponentTargetSelect))
  259.                 {
  260.                     // Capture it
  261.                     delegateComponent = CaptureComponent (delegateComponent, 
  262.                         (Component) self);
  263.                         
  264.                     // Keep references to the component we captured
  265.                     (*globals)->delegateComponent = delegateComponent;
  266.                     delegateComponentInstance = OpenComponent (delegateComponent);
  267.                     (*globals)->delegateComponentInstance = delegateComponentInstance;
  268.                     
  269.                     // Did we get an instance of the component we captured?
  270.                     if (delegateComponentInstance != 0L)
  271.                     {
  272.                         // Inform the component it has been captured
  273.  
  274.                         result = ComponentSetTarget (delegateComponentInstance, self);
  275.                         SetComponentInstanceStorage (self, (Handle) globals);
  276.                     }
  277.                     else    // Couldn't get an instance of the delegate component
  278.                     {
  279.  
  280.                         DisposHandle ((Handle) globals);
  281.                         result = kGenericError;
  282.                     }
  283.                 }
  284.                 else    // The component we need can't be captured
  285.                 {
  286.  
  287.                     DisposHandle ((Handle) globals);
  288.                     result = kGenericError;
  289.                 }
  290.  
  291.             }
  292.             else    // Couldn't find the delegate component
  293.             {
  294.                 DisposeHandle ((Handle) globals);
  295.                 result = kGenericError;
  296.             }
  297.         }
  298.         else    // NewHandleClear failed
  299.         {
  300.  
  301.             result = MemError();
  302.         }
  303.     }
  304.     else    // No more instances can be opened
  305.     {
  306.         result = kGenericError;
  307.     }
  308.     return (result);
  309. }
  310.  
  311. //-----------------------------------------------------------------------
  312.  
  313. pascal    ComponentResult    NuMathClose    (Handle                storage,
  314.                                          ComponentInstance    self)
  315. {
  316.     ComponentResult        result = noErr;
  317.     PrivateGlobals**    globals = (PrivateGlobals**) storage;
  318.     
  319.     // Do we have any clean up to do?
  320.     if (globals != nil)
  321.     {
  322.         // Any instances to close?
  323.         if ((*globals)->delegateComponentInstance != 0L)
  324.         {
  325.             // Close the captured component instance
  326.             result = CloseComponent ((*globals)->delegateComponentInstance);
  327.             (*globals)->delegateComponentInstance = 0L;
  328.             
  329.             // Uncapture the captured component (make it visible again)
  330.             result = UncaptureComponent ((*globals)->delegateComponent);
  331.             (*globals)->delegateComponent = 0L;
  332.         }
  333.         
  334.         // Dispose of globals
  335.         DisposeHandle ((Handle) globals);
  336.     }
  337.     return (result);
  338. }
  339.  
  340. //-----------------------------------------------------------------------
  341.  
  342. pascal    ComponentResult    NuMathCanDo    (short    selector)
  343. {
  344.     switch (selector)
  345.     {
  346.         // Component Manager request codes
  347.         case kComponentOpenSelect:
  348.         case kComponentCloseSelect:
  349.         case kComponentCanDoSelect:
  350.         case kComponentVersionSelect:
  351.         case kComponentRegisterSelect:
  352.         
  353.         // Math component request codes
  354.         case kDoDivideSelect:
  355.         case kDoMultiplySelect:
  356.         {
  357.             return (true);
  358.         }
  359.         
  360.         // Unsupported request codes
  361.         case kComponentTargetSelect:
  362.         default:
  363.         {
  364.             return (false);
  365.         }
  366.     }
  367. }
  368.  
  369. //-----------------------------------------------------------------------
  370.  
  371. pascal    ComponentResult    NuMathVersion    (void)
  372. {
  373.     // Return the version info
  374.     return (nuMathInterfaceRevision);
  375. }
  376.  
  377. //-----------------------------------------------------------------------
  378.  
  379. pascal    ComponentResult    NuMathRegister    (void)
  380. {
  381.     // See if a Math component is registered - if not, don't
  382.     // register this component, since it can't work without
  383.     // the Math component.  We return zero to register, one
  384.     // to not register.
  385.     ComponentDescription    mathDesc;
  386.     
  387.     mathDesc.componentType = mathComponentType;
  388.     mathDesc.componentSubType = 0L;
  389.     mathDesc.componentManufacturer = 'appl';
  390.     mathDesc.componentFlags = 0L;
  391.     mathDesc.componentFlagsMask = 0L;
  392.     
  393.     return ((FindNextComponent (nil, &mathDesc) != 0L) ? 0L : 1L);
  394. }
  395.  
  396. //-----------------------------------------------------------------------
  397.  
  398. pascal    ComponentResult    NuMathDoDivide    (short    numerator,
  399.                                          short    denominator,
  400.                                          short    *quotient)
  401. {
  402.     ComponentResult    result = noErr;
  403.     
  404.     // Check for zero denominator
  405.     if (denominator != 0)
  406.     {
  407.         *quotient = (short) Fix2Long 
  408.             (FixDiv (Long2Fix ((long) numerator), Long2Fix ((long) denominator)));
  409.     }
  410.     else    // Divide by zero not allowed
  411.     {
  412.         *quotient = 0;
  413.         result = kGenericError;
  414.     }
  415.     return (result);
  416. }
  417.  
  418. //-----------------------------------------------------------------------
  419.  
  420. pascal    ComponentResult    NuMathDoMultiply    (Handle    storage,
  421.                                               short    firstNum,
  422.                                              short    secondNum,
  423.                                              short    *multiplicationResult)
  424. {
  425.     PrivateGlobals**    globals = (PrivateGlobals**) storage;
  426.         
  427.     // Note that we need access to the component globals because
  428.     // we are delegating the multiply function to the captured
  429.     // Math component, and the component instance of the captured
  430.     // Math component is stored in the NuMath component globals.  In
  431.     // the MathDoMultiply function in the original Math component,
  432.     // we didn't require access to the component globals, and the
  433.     // interface for this function reflected this (there was no
  434.     // storage parameter).
  435.     return (DoMultiply ((*globals)->delegateComponentInstance, firstNum, 
  436.         secondNum, multiplicationResult));
  437. }
  438.  
  439. //-----------------------------------------------------------------------
  440.  
  441.  
  442.